<?php

namespace App\Services\Admin;

use Illuminate\Support\Facades\Auth;
use App\Services\Service;
use App\Models\Menu;
use App\Models\Role;

class MenuService extends Service
{

    public static function routes(): array
    {

        $user = Auth::user();

        $menu_ids = Role::whereIn('id', $user->roleIds)->pluck('menuIds')->toArray();
        $menu_ids = array_unique(array_merge(...$menu_ids));

        $list = Menu::query()->whereNotIn('type', [4])->whereIn('id', $menu_ids)->orderBy('sort', 'asc')->get()->toArray();

        $list = array_map(function ($item) {

            $resultList = [
                'id'        => $item['id'],
                'component' => $item['component'],
                'name'      => $item['routeName'] ?? $item['routePath'],
                'path'      => $item['routePath'],
                'redirect'  => $item['redirect'],
                'parentId'  => $item['parentId'],
                'meta'      => [
                    'alwaysShow' => (bool)$item['alwaysShow'],
                    'hidden'     => !(bool)$item['visible'],
                    'icon'       => $item['icon'] ?? '',
                    'keepAlive'  => (bool)$item['keepAlive'],
                    'params'     => $item['params'],
                    'title'      => $item['name']
                ]
            ];

            return $resultList;
        }, $list);

        return self::buildTreeNotParentId($list);
    }


    public static function options(?bool $onlyParent): array
    {

        $list = Menu::query()->select('id', 'name', 'parentId')->orderBy('sort', 'asc');

        if ($onlyParent) {
            $list->whereNotIn('type', [3, 4]);
        }

        $list = $list->get()->toArray();

        $list = array_map(fn($item) => [
            'value' => $item['id'],
            'label' => $item['name'],
            'parentId' => $item['parentId'],
        ], $list);


        return self::buildOptionsTree($list);
    }


    public static function index(array $params): array
    {

        $query = Menu::query()->orderBy('sort', 'asc');

        if (!empty($params['keywords'])) {
            $query->where('name', 'like', "%{$params['keywords']}%");
        }

        $list = $query->get()->makeVisible(['createTime', 'updateTime'])->toArray();

        return self::buildTree($list);
    }


    public static function store(array $data)
    {
        // 关于菜单目录类型，一定是没有 component 的，所以直接将 compone 赋值为 Layout
        if ($data['type'] == 2) {
            $data['component'] = 'Layout';
        }

        $menu = Menu::create($data);

        return [
            'id' => $menu->id,
        ];
    }

    public static function show(string $id)
    {
        $menu = Menu::find($id);

        if (!$menu) {
            self::throwValidationException('id', ['菜单不存在']);
        }

        return $menu->toArray();
    }

    public static function update(array $data, string $id): array
    {
        $menu = Menu::find($id);

        if (!$menu) {
            self::throwValidationException('id', ['菜单不存在']);
        }

        $menu->update($data);

        return [
            'id' => $menu->id,
        ];
    }

    public static function destroy(string $id): array
    {
        $menu = Menu::find($id);

        if (!$menu) {
            self::throwValidationException('id', ['菜单不存在']);
        }

        // 检查是否有子菜单
        $childCount = Menu::where('parentId', $id)->count();
        if ($childCount > 0) {
            self::throwValidationException('id', ['该菜单存在子菜单，无法删除']);
        }

        $menu->delete();

        return [
            'id' => $menu->id
        ];
    }
}
